package org.support.small.mallms.exception;

import lombok.extern.slf4j.Slf4j;
import org.springframework.util.StringUtils;
import org.springframework.validation.FieldError;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;
import org.support.small.mallms.model.Ret;
import org.support.small.mallms.utils.I18NUtils;

import javax.servlet.http.HttpServletResponse;
import java.util.stream.Collectors;

@Slf4j
@RestControllerAdvice
public class GlobalExceptionHandler {
    @ExceptionHandler(value = MethodArgumentNotValidException.class)
    public Ret<Void> handleMethodArgumentNotValidException(MethodArgumentNotValidException ex) {
        String errmsg = ex.getBindingResult().getAllErrors()
                .stream().map((error -> {
                    if (error instanceof FieldError) {
                        FieldError fieldError = (FieldError) error;
                        String fieldName = I18NUtils.getMessage(String.join(".", fieldError.getObjectName(), fieldError.getField()));
                        return String.format("【%s】%s", fieldName, fieldError.getDefaultMessage());
                    }
                    return error.getDefaultMessage();
                })).filter(StringUtils::hasText)
                .collect(Collectors.joining(";"));
        return Ret.fail(errmsg);
    }

    @ExceptionHandler(I18NCodeException.class)
    public Ret<Void> handleI18NCodeException(I18NCodeException ex) {
        String code = ex.getCode();
        String message = I18NUtils.getMessage(code, "system.error");
        return Ret.fail(message);
    }

    @ExceptionHandler(TokenForbiddenException.class)
    public Ret<Void> handleTokenExpiredException(TokenForbiddenException ex, HttpServletResponse response) {
        response.setStatus(HttpServletResponse.SC_FORBIDDEN);
        String message = I18NUtils.getMessage(ex.getCode());
        return Ret.fail(message);
    }

    @ExceptionHandler(Exception.class)
    public Ret<Void> handleException(Exception ex) {
        ex.printStackTrace();
        String message = I18NUtils.getMessage("system.error");
        return Ret.fail(message);
    }
}
